﻿using System;
using System.Design;
using System.Collections.Generic;
using System.ComponentModel;
using System.ComponentModel.Design;
using System.Text;
using System.ComponentModel.Design.Serialization;

namespace InfFront.InfoSources.Base.Design
{
    public enum InfoSourceDesignTimeActionTarget { Fields, FieldGroups, Commands };

    public interface IInfoSourceDesignTimeAction
    {
        string Caption { get; }

        InfoSourceDesignTimeActionTarget Target { get; }

        void Execute();
    }

    public interface IInfoSourceDesignTimeExtension
    {
        IDesigner Designer { get; set; }

        IEnumerable<IInfoSourceDesignTimeAction> Actions { get; }
    }


    public class InfoSourceDesignTimeExtension : IInfoSourceDesignTimeExtension
    {
        private List<IInfoSourceDesignTimeAction> actions;

        public InfoSourceDesignTimeExtension()
        {
            actions = new List<IInfoSourceDesignTimeAction>();
        }

        protected void AddAction(IInfoSourceDesignTimeAction action)
        {
            actions.Add(action);
        }

        #region IInfoSourceDesignTimeExtension Members

        public IDesigner Designer { get; set; }

        public IEnumerable<IInfoSourceDesignTimeAction> Actions
        {
            get { return actions; }
        }

        #endregion
    }

    public abstract class InfoSourceDesignTimeAction : IInfoSourceDesignTimeAction
    {
        public InfoSourceDesignTimeAction(InfoSourceDesignTimeExtension owner)
        {
            this.Owner = owner;
        }

        protected internal InfoSourceDesignTimeExtension Owner { get; set; }

        #region IInfoSourceDesignTimeAction Members

        public string Caption { get; set; }

        public InfoSourceDesignTimeActionTarget Target { get; set; }

        public abstract void Execute();

        #endregion
    }

    [AttributeUsage(AttributeTargets.Class, AllowMultiple = true, Inherited = true)]
    public class InfoSourceDesignTimeExtensionAttribute : Attribute
    {
        private string assemblyName;
        private string typeName;

        public InfoSourceDesignTimeExtensionAttribute(Type extensionType)
        {
            this.assemblyName = extensionType.Assembly.FullName;
            this.typeName = extensionType.FullName;
        }

        public InfoSourceDesignTimeExtensionAttribute(string assemblyName, string typeName)
        {
            this.assemblyName = assemblyName;
            this.typeName = typeName;
        }

        public IInfoSourceDesignTimeExtension CreateExtension()
        {
            var ext = (IInfoSourceDesignTimeExtension)Activator.CreateInstance(assemblyName, typeName).Unwrap();
            return ext;
        }
    }
}